import Foundation
import Combine
import CoreGraphics
import Vision

// 目标识别服务协议
protocol ObjectDetectionServiceProtocol {
    var detectedObjects: [DetectedObject] { get }
    var detectedObjectsPublisher: Published<[DetectedObject]>.Publisher { get }
    var isDetecting: Bool { get }
    
    func startDetection()
    func stopDetection()
}

// 目标识别服务
class ObjectDetectionService: ObservableObject, ObjectDetectionServiceProtocol {
    // MARK: - 属性
    @Published var detectedObjects: [DetectedObject] = []
    var detectedObjectsPublisher: Published<[DetectedObject]>.Publisher { $detectedObjects }
    
    @Published private(set) var isDetecting: Bool = false
    
    // 车辆控制服务
    private var controlService: CarControlService
    
    // 检测定时器
    private var detectionTimer: Timer?
    
    // 设置
    private var settings: AppSettings
    
    // MARK: - 初始化方法
    init(controlService: CarControlService, settings: AppSettings) {
        self.controlService = controlService
        self.settings = settings
        
        // 如果自动连接已启用，延迟启动检测
        if settings.isAutoConnectEnabled {
            DispatchQueue.main.asyncAfter(deadline: .now() + 4) { [weak self] in
                self?.startDetection()
            }
        }
    }
    
    // MARK: - 公共方法
    func startDetection() {
        // 仅在连接状态下开始检测
        guard controlService.carStatus.connectionStatus == .connected else {
            print("无法开始目标检测，设备未连接")
            return
        }
        
        // 停止现有定时器
        stopDetection()
        
        // 设置为正在检测状态
        isDetecting = true
        
        // 创建新的定时器，定期更新检测数据
        detectionTimer = Timer.scheduledTimer(withTimeInterval: 0.5, repeats: true) { [weak self] _ in
            self?.performDetection()
        }
        
        print("已开始目标检测")
    }
    
    func stopDetection() {
        // 停止检测定时器
        detectionTimer?.invalidate()
        detectionTimer = nil
        
        // 更新状态
        isDetecting = false
        
        print("已停止目标检测")
    }
    
    // MARK: - 私有方法
    private func performDetection() {
        // 在实际应用中，这里会处理摄像头图像并应用Vision框架进行检测
        // 这里我们模拟检测过程
        
        // 随机决定是否检测到新目标（70%几率）
        let detectNew = Double.random(in: 0...1) < 0.7
        
        if detectNew {
            // 创建一个模拟的检测目标
            createSimulatedObject()
        }
        
        // 更新现有目标的状态
        updateExistingObjects()
        
        // 移除过期的目标（超过5秒未更新）
        removeExpiredObjects()
    }
    
    private func createSimulatedObject() {
        // 选择随机目标类型
        let objectTypes: [ObjectType] = [.person, .car, .animal, .obstacle, .face]
        let randomType = objectTypes.randomElement() ?? .person
        
        // 根据类型设置不同的参数
        var confidence: Double = 0.0
        var distance: Double = 0.0
        
        switch randomType {
        case .person:
            confidence = Double.random(in: 0.75...0.95)
            distance = Double.random(in: 1.5...5.0)
        case .car:
            confidence = Double.random(in: 0.80...0.98)
            distance = Double.random(in: 3.0...10.0)
        case .animal:
            confidence = Double.random(in: 0.65...0.85)
            distance = Double.random(in: 1.0...4.0)
        case .obstacle:
            confidence = Double.random(in: 0.70...0.90)
            distance = Double.random(in: 0.5...3.0)
        case .face:
            confidence = Double.random(in: 0.80...0.97)
            distance = Double.random(in: 1.0...3.0)
        case .unknown:
            confidence = Double.random(in: 0.50...0.70)
            distance = Double.random(in: 2.0...6.0)
        }
        
        // 选择随机行为
        let behaviors: [ObjectBehavior] = [.walking, .running, .standing, .sitting, .moving]
        let randomBehavior = behaviors.randomElement() ?? .unknown
        
        // 生成随机边界框
        let x = Double.random(in: 0.1...0.7)
        let y = Double.random(in: 0.1...0.7)
        let width = Double.random(in: 0.1...0.3)
        let height = Double.random(in: 0.1...0.3)
        let boundingBox = CGRect(x: x, y: y, width: width, height: height)
        
        // 创建检测对象
        let newObject = DetectedObject(
            type: randomType,
            confidence: confidence,
            distance: distance,
            behavior: randomBehavior,
            trackingStatus: .found,
            boundingBox: boundingBox
        )
        
        // 添加到检测列表
        detectedObjects.append(newObject)
        
        // 如果列表过长，移除最旧的对象
        if detectedObjects.count > 5 {
            detectedObjects.removeFirst()
        }
        
        print("检测到新目标: \(randomType.rawValue), 置信度: \(confidence), 距离: \(distance)米")
    }
    
    private func updateExistingObjects() {
        // 更新现有目标的状态
        for i in 0..<detectedObjects.count {
            // 避免越界访问
            guard i < detectedObjects.count else { continue }
            
            // 随机决定是否更新此目标
            if Double.random(in: 0...1) < 0.8 {
                var object = detectedObjects[i]
                
                // 稍微调整距离和位置
                object.distance += Double.random(in: -0.3...0.3)
                object.distance = max(0.1, object.distance)
                
                // 调整边界框位置
                var box = object.boundingBox
                box.origin.x += CGFloat.random(in: -0.02...0.02)
                box.origin.y += CGFloat.random(in: -0.02...0.02)
                // 确保边界框不超出范围
                box.origin.x = max(0, min(1 - box.width, box.origin.x))
                box.origin.y = max(0, min(1 - box.height, box.origin.y))
                object.boundingBox = box
                
                // 随机调整行为
                if Double.random(in: 0...1) < 0.1 {
                    let behaviors: [ObjectBehavior] = [.walking, .running, .standing, .sitting, .moving]
                    object.behavior = behaviors.randomElement() ?? object.behavior
                }
                
                // 更新跟踪状态
                if Double.random(in: 0...1) < 0.95 {
                    object.trackingStatus = .tracking
                } else {
                    object.trackingStatus = .lost
                }
                
                // 更新时间戳
                object.lastUpdatedTime = Date()
                
                // 更新对象
                detectedObjects[i] = object
            }
        }
    }
    
    private func removeExpiredObjects() {
        // 移除5秒未更新的目标
        let currentTime = Date()
        detectedObjects = detectedObjects.filter { object in
            let timeSinceLastUpdate = currentTime.timeIntervalSince(object.lastUpdatedTime)
            return timeSinceLastUpdate < 5.0
        }
    }
    
    deinit {
        // 清理定时器
        detectionTimer?.invalidate()
    }
} 